package com.base.netlib.observer

import com.base.netlib.NetLib
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.catch

interface ResponseObserver<T> {
    suspend fun dealError(error: Throwable)
}

open class DefaultResponseObserver<T> : ResponseObserver<T> {
    var error: Throwable? = null

    var data: T? = null
    override suspend fun dealError(error: Throwable) {
        // 通知错误
        NetLib.netErrorFlow.emit(error)
    }
}

/**
 * 成功回调  必须调用才会发起请求
 * @param block 成功回调
 */
suspend inline fun <T, reified R : DefaultResponseObserver<T>> Flow<T>.onSuccess(crossinline block: (data: T) -> Unit): DefaultResponseObserver<T> {
    val observer = R::class.java.newInstance()
    catch {
        it.printStackTrace()
        observer.error = it
    }.collect { value ->
        observer.data = value
        block.invoke(value)
    }
    return observer
}

/**
 * 失败回调 不调用就不会处理错误
 * @param block 失败回调  返回值 是否自己处理错误不交由统一处理 false自己不处理 统一处理错误
 */
suspend inline fun <T> DefaultResponseObserver<T>.onError(block: (error: Throwable) -> Boolean): DefaultResponseObserver<T> {
    error?.also {
        if (!block.invoke(it)) {
            dealError(it)
        }
    }
    return this
}